class Person(object):
    pass
a = Person()
b = Person()

print a == b
print a is b

# ---------------------------
class Person(object):
    pass

p1 = Person()
p1.name = 'Bart'

p2 = Person()
p2.name = 'Adam'

p3 = Person()
p3.name = 'Lisa'

L1 = [p1, p2, p3]
L2 = sorted(L1, key = lambda x: x.name)

print L2[0].name
print L2[1].name
print L2[2].name


# 初始化实力
# 双下划线开头的"__gender"不能直接被外部访问也不可以在子类中使用。 私有属性
# 如果一个属性以"__xxx__"的形式定义 就可以访问，并且为特殊属性
# _xxx 可以在子类中使用。
class Person(object):
    def __init__(self, name, gender, birth, job):
        self.name = name
        self.__gender = gender
        self.birth = birth
        self.job = job

xiaoming = Person('Xiao Ming', 'Male', '1990-1-1', job='Student')
print xiaoming.name
print xiaoming.job

# example
class Person(object):
    def __init__(self, name, score):
        self.name = name
        self.__score = score
p = Person('Bob', 59)
print p.name
try:
    print p.__score
except AttributeError:
    print ('attributeError')


# 继续 实例上更新属性只能改自己的
class Person(object):
    count = 0
    def __init__(self, name):
        Person.count += 1
p1 = Person('Bob')
print Person.count
p2 = Person('Alice')
print Person.count
p3 = Person('Tim')
print Person.count

# -------------------------------
class Person(object):
    def __init__(self, name, score):
        self.__name = name
        self.__score = score

    def get_grade(self):
        if self.__score >= 80:
            return 'A'
        if self.__score >= 60:
            return 'B'
        return 'C'

p1 = Person('Bob', 90)
p2 = Person('Alice', 65)
p3 = Person('Tim', 48)

print p1.get_grade()
print p2.get_grade()
print p3.get_grade()



# 在class中定义的全部是实例方法，实例方法第一个参数 self 是实例本身
# 通过标记一个 @classmethod，该方法将绑定到 Person 类上，而非类的实例。
# 类方法的第一个参数将传入类本身，通常将参数名命名为 cls
class Person(object):
    __count = 0

    @classmethod
    def how_many(cls):
        return cls.__count
    def __init__(self, name):
        self.name = name
        Person.__count += 1

print Person.how_many()
p1 = Person('Bob')
print Person.how_many()
